package utils

import (
	"errors"
	"gitee.com/Frank098/devops-app-mgt/utils/log"
	"github.com/dgrijalva/jwt-go"
	"time"
	//"golang.org/x/oauth2/jwt"
)

var JWTToken jwtToken

type jwtToken struct{}

// 定义token中携带的信息
type CustomClaims struct {
	Username string `json:"username"`
	jwt.StandardClaims
}

// TokenExpireDuration token的过期时长
const TokenExpireDuration = time.Hour * 2

// 加解密因子
var SECRET = []byte("gWdO%vqYFnGFvFR5Ud4*)cTax83taxw0T^Hi8)x0nWBEfF$PYLw5%(i%T50Q7JUC^96%ECzi2@4AZ@^V1I%Dg1$!&oK%dv7~K")

// GenToken 生成JWT
func GenToken(username string) (string, error) {
	c := CustomClaims{
		username, // 自定义字段
		jwt.StandardClaims{
			ExpiresAt: time.Now().Add(TokenExpireDuration).Unix(), // 过期时间
			Issuer:    "Frank",                                    // 签发人
		},
	}
	// 使用指定的签名方法创建签名对象
	token := jwt.NewWithClaims(jwt.SigningMethodHS256, c)
	// 使用指定的secret签名并获得完整的编码后的字符串token
	return token.SignedString(SECRET)
}

// 解析Token
func (*jwtToken) ParseToken(tokenString string) (claims *CustomClaims, err error) {
	token, err := jwt.ParseWithClaims(tokenString, &CustomClaims{}, func(token *jwt.Token) (interface{}, error) {
		return []byte(SECRET), nil
	})
	if err != nil {
		log.Error("parse token failed ", err)
		//处理token解析后的各种错误
		if ve, ok := err.(*jwt.ValidationError); ok {
			if ve.Errors&jwt.ValidationErrorMalformed != 0 {
				return nil, errors.New("TokenMalformed")
			} else if ve.Errors&jwt.ValidationErrorExpired != 0 {
				return nil, errors.New("TokenExpired")
			} else if ve.Errors&jwt.ValidationErrorNotValidYet != 0 {
				return nil, errors.New("TokenNotValidYet")
			} else {
				return nil, errors.New("TokenInvalid")
			}
		}
	}

	if claims, ok := token.Claims.(*CustomClaims); ok && token.Valid {
		return claims, nil
	}
	return nil, errors.New("解析Token失败")
}
